import CryptoJS from 'crypto-js';

/**
 * 确保密钥的长度为指定的字节数（例如：16 字节）
 * @param {string} secretKey - 原始密钥
 * @param {number} length - 目标长度（以字节为单位）
 * @returns {string} - 填充或截断后的密钥
 */
export const normalizeKeyLength = (secretKey, length = 16) => {
    // 如果密钥长度小于目标长度，则填充
    if (secretKey.length < length) {
        return secretKey.padEnd(length, '0');  // 使用 '0' 填充
    }
    // 如果密钥长度大于目标长度，则截断
    if (secretKey.length > length) {
        return secretKey.substring(0, length);  // 截断多余的字符
    }
    return secretKey;
};

/**
 * 使用 AES 加密数据
 * @param {string} data - 要加密的数据
 * @param {string} secretKey - 加密的密钥
 * @returns {string} - Base64 编码的加密数据（包含 IV）
 */
export const encryptData = (data, secretKey) => {
    // 确保密钥长度为 16 字节（AES-128）
    const normalizedKey = normalizeKeyLength(secretKey, 16);
    const key = CryptoJS.enc.Utf8.parse(normalizedKey);  // 转为 WordArray 格式

    // 随机生成 16 字节的 IV
    const iv = CryptoJS.lib.WordArray.random(16);

    // 使用 AES 加密，CBC 模式，PKCS7 填充
    const encrypted = CryptoJS.AES.encrypt(data, key, { iv: iv, padding: CryptoJS.pad.Pkcs7 });

    // 将 IV 和加密数据合并，先是 IV，然后是密文
    const combinedData = iv.concat(encrypted.ciphertext);

    // 返回 Base64 编码的加密数据（包括 IV）
    return CryptoJS.enc.Base64.stringify(combinedData);
};

/**
 * 使用 AES 解密数据
 * @param {string} encryptedData - Base64 编码的加密数据（包含 IV）
 * @param {string} secretKey - 解密的密钥
 * @returns {string} - 解密后的数据
 */
export const decryptData = (encryptedData, secretKey) => {
    // 首先解码 Base64 编码的加密数据
    const encryptedBytes = CryptoJS.enc.Base64.parse(encryptedData);

    // 提取前 16 字节作为 IV
    const iv = CryptoJS.lib.WordArray.create(encryptedBytes.words.slice(0, 4)); // 16 字节 IV 对应前 4 个整数（每个整数 4 字节）

    // 提取剩余部分为密文
    const ciphertext = CryptoJS.lib.WordArray.create(encryptedBytes.words.slice(4));

    // 确保密钥长度为 16 字节（AES-128）
    const normalizedKey = normalizeKeyLength(secretKey, 16);
    const key = CryptoJS.enc.Utf8.parse(normalizedKey);  // 转为 WordArray 格式

    // 解密数据
    const bytes = CryptoJS.AES.decrypt({ ciphertext: ciphertext }, key, { iv: iv, padding: CryptoJS.pad.Pkcs7 });
    const decrypted = bytes.toString(CryptoJS.enc.Utf8);  // 转换为字符串

    return decrypted;
};

